home *** CD-ROM | disk | FTP | other *** search
/ Developer CD Series 1998 January: Mac OS SDK / Dev.CD Jan 98 SDK2.toast / Development Kits (Disc 2) / QuickTime / Sample Code / QT Codec Acceleration / MPEG YCrCb codec info next >
Encoding:
Text File  |  1997-02-26  |  9.8 KB  |  210 lines  |  [TEXT/R*ch]

  1. YCrCb Codec Info.
  2.  
  3. The MPEG decoder engine produces planar Y'CrCb data in a single block of
  4. data that is passed on to the ICM for display.
  5.  
  6. Some basic properties of this block of data are specified in the
  7. ImageDescription created for the picture (or sequence of pictures) and
  8. this data can be accessed from ICM in the usual fashion. Such
  9. information includes the width and height of the Y'CrCb data, and the
  10. length of this block of data representing the image.
  11.  
  12. The block of data itself is in the form of a YCrCbVideoFrame struct, defined as
  13.  
  14.     struct YCrCbVideoFrame
  15.     {
  16.         //These are publicly defined fields.
  17.         UInt32 headerSize;
  18.         UInt16 luminanceOffset, cbOffset, crOffset;
  19.         UInt16 luminanceRowBytes, chromaRowBytes;
  20.     
  21.         //Following, here, is the actual Y, cR and cB data.
  22.     };
  23.     typedef struct YCrCbVideoFrame YCrCbVideoFrame;
  24.     #define kYCrCb420Type 'mpyc'
  25.  
  26. The headerSize is right now set to sizeof(YCrCbVideoFrame)==14 bytes.
  27. Conceivably that could change in the future.
  28.  
  29. The more interesting information is the luminanceOffset, cbOffset, and
  30. crOffset fields. The luminance, cB and cR data is stored as three planes
  31. of data, specified by a ptr in memory and a rowbytes, just like a
  32. pixmap. The height of the luminance data is given by the height passed
  33. on to ICM. The height of the cR and cB data is half that. (Note that the
  34. height passed on to ICM will be, per the MPEG specs, a multiple of 16,
  35. ie a multiple of a macroblock height. Likewise the width will be as
  36. multiple of 16.) One might imagine that the rowBytes information is
  37. redundant, that it would simply equal the width of the picture. This is
  38. not true for two reasons. The first is that the widths of rows are
  39. padded by some number of bytes to stride different rows starting at
  40. different offsets in a cache line and thus making the MPEG engine
  41. faster. The second is that the luminance and chroma data are interleaved
  42. with each other (in a fashion that will not be described further because
  43. it may change).
  44.  
  45. So in one's routine for actually displaying this data one will use code
  46. that looks something like
  47.  
  48. pascal ComponentResult YCrCbDisplayFrame(SomeStruct* myVariousStuffStruct, 
  49.   YCrCbVideoFrame* framePtr)
  50. {
  51.     UInt8* luminancePtr;
  52.     UInt8* cRPtr;
  53.     UInt8* cBPtr;
  54.  
  55.     luminancePtr=((UInt8*)ycrcbVideoFrame) +ycrcbVideoFrame->luminanceOffset;
  56.     cRPtr       =((UInt8*)ycrcbVideoFrame) +ycrcbVideoFrame->crOffset;
  57.     cBPtr       =((UInt8*)ycrcbVideoFrame) +ycrcbVideoFrame->cbOffset;
  58.     
  59.     /*
  60.     Now run over these arrays, with loops that look like    
  61.     for(h=0; h<myVariousStuffStruct->srcHeight; h+=2){
  62.         for(w=0; w<myVariousStuffStruct->srcWidth; w+=2){
  63.             cr =*cRPtr++;
  64.             cb =*cBPtr++;
  65.             y00=luminancePtr[0];
  66.             y01=luminancePtr[1];
  67.             y10=(luminancePtr+ framePtr->luminanceRowBytes)[0];
  68.             y11=(luminancePtr+ framePtr->luminanceRowBytes)[1];
  69.             luminancePtr+=2;
  70.             //Do some stuff with y, cr, cb to get them to the screen.
  71.         }
  72.         cRPtr+=       ( framePtr->chromaRowBytes - myVariousStuffStruct->srcWidth/2 );
  73.         cBPtr+=       ( framePtr->chromaRowBytes - myVariousStuffStruct->srcWidth/2 );
  74.         luminancePtr+=( framePtr->luminanceRowBytes*2 - myVariousStuffStruct->srcWidth );
  75.     }
  76. }
  77.  
  78. Now a few notes.
  79.  
  80. The type of this codec is 'mpyc'.
  81.  
  82. I have stuck to the exact terminology of Y'CrCb, although in colloquial
  83. speech one tends to use YUV as easier to pronounce. Y'CrCb is precisely
  84. define in CCIR recommendation 601 (now renamed ITU-R BT 601). If you are
  85. unfamiliar with details of this, I would recommend reading details of
  86. it. The easiest way to find such details is to use any web search engine
  87. with the keywords CCIR 601 and read two or three of the documents that
  88. result. Many of these documents (for example the ColorSpaces FAQ)
  89. describe in great detail the points I touch on below.
  90.  
  91. Here are some points to note about Y'CrCb.  Most of these are subtle
  92. points that can be ignored in one's first pass at attempting to get
  93. things to work. Once things work acceptably, one may want to return to
  94. these points to ensure that onscreen display is not merely acceptable
  95. but as good as possible.
  96.  
  97. • WHAT ABOUT GAMMA CORRECTION?
  98. The Y' component is gamma corrected. This will affect how and where you
  99. place gamma correction in your card design, and if your card is designed
  100. for both PCs and Macs you may want to have it toggle between two
  101. different modes to get the gamma correction correct on both systems.
  102.  
  103. • WHAT ABOUT DIGITAL VIDEO PINNING?
  104. Y' has a nominal range of 16 through 235. 16 and values below are pure
  105. black, 235 and values above are pure white. Values in between increase
  106. linearly in brightness. The colorspace conversion may choose to ignore
  107. this nicety and simply map 0 to black, 235 to white, in the usual
  108. fashion. However this can lead to regions of black looking noticably
  109. noisy because random values between 01 and 16 that appear in those
  110. regions, and that are all supposed to map to black, instead map to
  111. noticably different blacks. Likewise the chroma components have nominal
  112. values between 16 and 240, however ignoring those is pretty harmless in
  113. terms of visual damage.
  114.  
  115. • WHAT ABOUT ALTERNATIVE COLOR SAMPLING, EG 4:4:4?
  116. Right now we only deal with MPEG-1 and thus we only deal with 4:2:0
  117. format (ie chroma is subsampled by 2 in both the horizontal and vertical
  118. directions). At some point we'll add support for MPEG2 at which point
  119. we'll have to deal with other chroma subsampling formats like 4:2:2 and
  120. 4:4:4. This will be handled by defining additional codec types for those
  121. formats (though presumably your code for building those codecs will
  122. share the same code base as your code for this 4:2:0 codec).
  123.  
  124. • WHAT ABOUT SCALING?
  125. Your codec MUST deal with scaling. If it does not, it is essentially
  126. useless. Pretty much all MPEG video is encoded with an aspect ration
  127. that is not 1, eg the video is encoded at 352x240 samples but it is
  128. supposed to be displayed in a 320x240 window on a monitor with square
  129. pixels. If your codec cannot cope with scaling, it will not be used and
  130. the software YCrCb codec will be used.
  131.  
  132. What is obviously optimal is if your card can do scaling in the card. If
  133. that is not possible, what might be best is for your card to scale the
  134. data as it is reading it in from the  YCrCbVideoFrame* data pointer and
  135. writing it out to your card's buffers. In addition it is not ideal to
  136. hardcode scaling at one value, say 352x240 scaled to 320x240. That is
  137. the scaling that is used for NTSC video, but footage derived from PAL
  138. video will use different scaling again. Footage from film, or generated
  139. by computer might use different scaling again.
  140.  
  141. While scaling is pretty much non-negotiable, your codec has the option
  142. of not bothering with clipping, or with some bit depths. Just as with
  143. any other codec, if you cannot deal with clipping, or with a 4-bit
  144. screen depth or whatever, you simply make this known in your
  145. PreDecompress() call and ICM will cover for you. Unlike scaling,
  146. clipping and screen depths other than those you are built to support
  147. (presumably 24bit, 16bit and maybe 8bit color or 8bit grey) are not
  148. common cases.
  149.  
  150. • WHAT ABOUT SOURCE EXTRACTION?
  151. Consider a source image (compressed as YCrCb) that one wishes to
  152. display. QuickTime has always had a facility for specifying a source
  153. rectangle within that source image that is smaller than the entire
  154. image. Now practically every MPEG stream has visual gunk of one sort or
  155. another around the edges, two or three pixels worth.  The MPEG system
  156. allows the user to specify a "masking out" of that visual junk by
  157. defining a source rectangle from the images that omits this junk. What
  158. this means for you is that your hardware/codec must be able to handle
  159. source extraction.  If you simply ignore it and rely on ICM to do the
  160. work for you, as with scaling, you will be useless for practically all
  161. MPEG playback.
  162.  
  163. • WHAT ABOUT GREY-SCALE INPUT?
  164. The YCrCb input is almost always "24bit" input in the sense that the Y,
  165. cR and cB values are 8bit values. However that input may also be, in a
  166. sense, 8-bit grey input if some preference has been set asking the MPEG
  167. decoder not to decode color. In this case image description describing
  168. the input data will still say that the data is 24bit, but the cbOffset,
  169. crOffset, and chromaRowBytes fields of the YCrCbVideoFrame will be set
  170. to 0.
  171.  
  172. Note that this is a property of the input format and is orthogonal to
  173. the screen display format. You may have color input (valid Y', cR and cB
  174. data) coming in for display to an 8-bit grey screen (although in that
  175. case you would simply ignore the chroma data and display only Y').
  176. Alternatively you could have grey scale data coming in (Y valid but
  177. chroma offsets and rowBytes set to 0) for display on a color 16bit
  178. screen. (This latter case might occur if the user has decided they want
  179. smoother motion at the expense of color and so tell the MPEG decode
  180. engine not to bother decoding color.)
  181.  
  182. • WHAT ARE THE DETAILS OF THE COLOR-CONVERSION MATRICES?
  183. The color conversion matrix used is 
  184.     R'=Y^             + 1.40200*Cr^
  185.     G'=Y^- 0.34414*Cb^- 0.71414*Cr^
  186.     B'=Y^+ 1.77200*Cb^
  187.  
  188.     where Cr^ = scale(Cr-128) ie the value from the cR array (which is in the range 
  189.     0, 255) with 128 subtracted from it and scaled to the [16, 240] range, 
  190.     ie Cr^= [256/(240-16)]*(cr-128).
  191.     likewise Cb^=[256/(240-16)]*(cr-128).
  192.     Y^=[256/(235-16)](Y'-16).
  193.  
  194.  
  195. An alternative formulation, with the scaling directly in the matrix is
  196.     R'=1.16(Y'-16)                  + 1.594 (cr-128)
  197.     G'=1.16(Y'-16) - 0.392 (cb-128) - 0.813 (cb-128)
  198.     B'=1.16(Y'-16) + 2.017 (cb-128)
  199.     
  200.  
  201. If you read different books you will see slightly different versions of
  202. the above. Quite how accurate one wishes to be depends on the CPU or
  203. transistor budget one throws at the problem. Details of exactly how the
  204. scaling is done are reasonably flexible within limits -- as long as the
  205. clamping of black Y' at 16 is respected one can ignore a few of the
  206. finicky details of the above if ignoring is convenient. One is welcome
  207. to use hardware/software that is designed for JPEG (which uses slightly
  208. different matrices) and the result may be acceptable to some users---but
  209. not to others.
  210.